<?php
/**
 * 模板模式
 * 定义一个操作中的算法的骨架，而将一些步骤延迟到子类中。
 * Template Method使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。
 *二、应用场景
 *Template Method模式非常简单，但是在面向对象系统中有着大量的应用。
 * 比如我们先提供一个父类,然后先把固定不变的算法放在父类中实现，但是一些可变的行为就先不实现它，留给子类实现。这时候我们发布出去了，如果使用者需要扩展功能，则你可以继承这个抽象类，然后覆写里面的抽象方法或virturl方法，再然后就调用一个类似的execute方法（父类定义好的），就完成了扩展开发，所以这个模式有着大量的应用。
 *另外这个模式也是把各子类的公共行为提取到父类中，避免了代码重复。
 *三、代码实现
 *比如模仿动物的叫声，我们先定义一个算法的骨架，
 * 一个Animal类，这个类里，我们有一个Shout的方法，但是这个方法又从GetShout方法来获取值，
 * GetShout方法要延迟要子类去实现。
 *模版方法很简单，但用途很广，他允许我们先定义好算法骨架，然后让具体实现由子类来实现，因此可以进行扩展开发。另外也是代码复用的基本技术，如果代码高度类似，可以考虑用模版方法去除重复。
 *
 */

class Animal{
    public function Shout(){
      return $this->GetShout();
    }

    protected function GetShout(){
        return null;
    }

}

class Cat extends Animal{
    protected function GetShout(){
        return "猫";
    }
}

class Dog extends Animal{
    protected function GetShout()
    {
        return "狗";
    }
}

 $animal =new Cat();
$shout=$animal->Shout();
echo $shout;
/**
 * 四、总结
 *模版方法很简单，但用途很广，他允许我们先定义好算法骨架，
 * 然后让具体实现由子类来实现，因此可以进行扩展开发。
 * 另外也是代码复用的基本技术，如果代码高度类似，可以考虑用模版方法去除重复。
 */